grammar eval;

options {
	language = Python;
}

@members {
	# Map variable name to Integer object holding value
	memory = dict()
}

prog:   stat+ ;

stat:   expr NEWLINE {print($expr.value)}
		|   ID '=' expr NEWLINE
			{self.memory[$ID.text] = int($expr.value)}
		|   NEWLINE
;

expr returns [int value]
		:   e=multExpr {$value = $e.value}
		(   '+' e=multExpr {$value += $e.value}
		|   '-' e=multExpr {$value -= $e.value}
		)*
;

multExpr returns [int value]
		:   e=atom {$value = $e.value} ('*' e=atom {$value *= $e.value})*
; 

atom returns [int value]
		:   INT {$value = int($INT.text)}
		|   ID
		{
			if $ID.text in self.memory:
				$value = self.memory[$ID.text]
			else:
				print('undefined variable '+$ID.text)
		}
		|   '(' expr ')' {$value = $expr.value}
;

ID  :   ('a'..'z'|'A'..'Z')+ ;
INT :   '0'..'9'+ ;
NEWLINE:'\r'? '\n' ;
WS  :   (' '|'\t')+ {skip();} ;

